ARD2  RC2
Airbag Reference Demonstrator using MPC5604P
Error_State.c
Go to the documentation of this file.
00001 
00016 #include "derivative.h"
00017 #include "Compile_Options.h"
00018 #include "Error_State.h"
00019 #include "SM.h"
00020 #include "HAL.h"
00021 #include "SBC_AL.h"
00022 #include "Central_Accel_AL.h"
00023 #include "MailScheduler.h"
00024 #include "Application_Globals.h"
00025 #include "SIU.h"
00026 #include "Init_State.h"
00027 #ifdef USE_LABVIEW
00028 #include "Labview.h"
00029 #endif
00030 /*
00031  ******************************************************************************
00032  * Constants
00033  ******************************************************************************
00034  */
00036 static const uint16_t cau16PreErrorValidStates[] =
00037 {
00038   SM_STATE_SETUP, SM_STATE_ERROR, SM_APPLICATION_START, SM_STATE_DECISION,
00039   SM_STATE_DEPLOYMENT, SM_STATE_SYSTEM_TEST, SM_STATE_GUI };
00042 static uint32_t (* const u32pfnErrorTreatment[])(void) =
00043 {
00044   &u32fnSMInitError, &u32fnStateErrorError, &u32fnStateAcquisitionError,
00045   &u32fnStateDecisionError, &u32fnStateDeploymentError,
00046   &u32fnStateSystemTestError, &u32fnStateGUIError };
00047 #ifdef USE_LABVIEW
00048 static const uint8_t cau8ErrorGUIMsg01[] = "Catastrophic error. Safe mode entered.";
00049 static const uint8_t cau8ErrorGUIMsg02[] = "An error occurred. Some functionality may have been lost.";
00050 #endif
00051 /*
00052  ******************************************************************************
00053  * Globals
00054  ******************************************************************************
00055  */
00056 /*
00057  ******************************************************************************
00058  * u32fnStateError
00059  ******************************************************************************
00060  */
00061 uint32_t u32fnStateError(void)
00062 {
00063   uint32_t u32Status;
00064   
00065   /* Verify that we can execute - Previous state ended correctly */
00066   u32Status = u32fnSMValidateCurrentState((uint16_t*)cau16PreErrorValidStates,
00067                                           N_ELEMENTS(cau16PreErrorValidStates));
00068   if(CLEAR == u32Status)
00069   {
00070     /* Here comes the real contents of the state */
00071     LOCK_STATE_EXECUTION();
00072     
00073     /* We will behave differently depending on the error flags and what */
00074     /* caused them, but there are some general cases, as shown below    */
00075     if(gu32SMStateStatus & (SM_INVALID_SOURCE_STATE))
00076     {
00077       /* Catastrophic failure, stop everything */
00078       u32Status = u32fnSafeMode();
00079     }
00080     else
00081     {
00082       /* Treat errors according to different conditions */
00083       u32Status = u32pfnErrorTreatment[gu16SMCurrentState[SM_PREVIOUS_STATE]]();
00084     }
00085   }
00086   else
00087   {
00088     /* Leave */
00089   }
00090 
00091   /* Set the next state */
00092   if(CLEAR != u32Status)
00093   {
00094     vfnSMWriteNextState(SM_STATE_ERROR);
00095   }
00096   else
00097   {
00098     /* We assume that each sub-routine has pointed to the next state */
00099 #ifdef USE_LABVIEW
00100     /* If we've made it this far, we are going back to the application. Signal the GUI */
00101     vfnDisplayGUIErrorMessage();
00102 #endif
00103   }
00104   
00105   /* Unlock the state */
00106   UNLOCK_STATE_EXECUTION();
00107   
00108   return (u32Status);
00109 }
00110 /*
00111  ******************************************************************************
00112  * u32fnSafeMode
00113  ******************************************************************************
00114  */
00115 static uint32_t u32fnSafeMode(void)
00116 {
00117   uint32_t u32Status;
00118   uint16_t u16InputPinBehavior;
00119   
00120 #ifdef USE_LABVIEW
00121   vfnLVEnable(TRUE);
00122   (void)u8fnLVWaitForTxPort();
00123   (void)u8fnLabViewSendMSorMP((uint8_t*)&cau8ErrorGUIMsg01, sizeof(cau8ErrorGUIMsg01),
00124                               LV_SEND_SERIALLY, LV_MP_MSG);
00125 #endif  
00126   
00127   /* EN_FL must never go high by accident. Make it an input. */
00128   u16InputPinBehavior = PIN_GPI_DEFAULT_CONFIG;
00129   vfnConfigDefaultPinBehavior((const uint16_t*)&u16InputPinBehavior,
00130                               u8fnReturnPinIndex(PIN_EN_FL), TRUE);
00131   
00132   /* Disarm all squibs  */
00133 
00134   /* Stop WD1 signal to CG147 */
00135 
00136   /* Stop scheduler (and with it, all automatic watch-dog updates) */
00137   (void)u8fnLaunchScheduler(CLEAR);
00138   
00139   /* Go into STOP mode */
00140 //  vfnEnterLowPowerMode();
00141   
00142   for(;;)
00143   {
00144     /* We are not going anywhere */
00145   }
00146   return (u32Status);
00147 }
00148 /*
00149  ******************************************************************************
00150  * u32fnSMInitError
00151  ******************************************************************************
00152  */
00153 static uint32_t u32fnSMInitError(void)
00154 {
00155   uint32_t u32Status;
00156   uint8_t u8Counter1;
00157   uint8_t u8Counter2;
00158   uint32_t u32Mask;
00159   
00160   /* Init local variables */
00161   u32Status = CLEAR;
00162   u8Counter1 = CLEAR;
00163   
00164   /* Trap the cases where we should not go anywhere. */
00165   if(gu32SMStateStatus & (INIT_STATE_CA_ERROR | INIT_STATE_MCU_ERROR
00166       | INIT_STATE_SBC_ERROR))
00167   {
00168     u32Status = u32fnSafeMode();
00169   }
00170   else
00171   {
00172     /* Turn the lamp on */
00173     (void)u8fnSBCEnableWarningLamp(TRUE);
00174     
00175     /* These situations should allow for partial behavior of our system */
00176     if(gu32SMStateStatus & SBC_TEST_ALL_SAT)
00177     {
00178       /* SATELLITE PROBLEM */
00179       /* Remove the satellite from the active satellite list */
00180       gu16ActivePSI5Channels
00181           = u16fnErrorRemoveFromList(gu16ActivePSI5Channels,
00182                                      (uint16_t)gu32SMStateStatus);
00183       /* And remove the associated squibs as well */
00184       for(u32Mask = BIT0; u32Mask < BIT12; u32Mask <<= BIT0)
00185       {
00186         if(gu32SMStateStatus & u32Mask)
00187         {
00188           for(u8Counter2 = CLEAR; u8Counter2 < cu8SizeOfSatToSquibs; u8Counter2 += 2u)
00189           {
00190             if(cau8SatToSquibs[u8Counter2] == u8Counter1)
00191             {
00192               gu16ActiveSquibChannels = u16fnErrorRemoveFromList(gu16ActiveSquibChannels,
00193                                          BIT0 << (cau8SatToSquibs[u8Counter2 + 1u]));
00194             }
00195             else
00196             {
00197               /* Nothing */
00198             }
00199           }
00200         }
00201         else
00202         {
00203           /* Nothing */
00204         }
00205         u8Counter1++;
00206       }
00207     }
00208     else
00209     {
00210       /* Nothing */
00211     }
00212     if(gu32SMStateStatus & SBC_TEST_ALL_SQUIB)
00213     {
00214       /* Squib problem */
00215       /* Remove the squib from the active squib list */
00216       gu16ActiveSquibChannels
00217           = u16fnErrorRemoveFromList(gu16ActiveSquibChannels,
00218                                      (uint16_t)(gu32SMStateStatus >> BITS_IN_16));
00219     }
00220     else
00221     {
00222       /* Nothing */
00223     }
00224     
00225     /* If we have no squibs or satellites, it's the end of the road for us */
00226     if((CLEAR == gu16ActivePSI5Channels) || (CLEAR == gu16ActiveSquibChannels))
00227     {
00228       /* Not much more left to do */
00229       u32Status = u32fnSafeMode();
00230     }
00231     else
00232     {
00233       /* Nothing */
00234     }
00235     
00236     /* Choose the next state */
00237     vfnSMWriteNextState(SM_APPLICATION_START);
00238   }
00239   
00240   return (u32Status);
00241 }
00242 /*
00243  ******************************************************************************
00244  * u32fnStateErrorError
00245  ******************************************************************************
00246  */
00247 static uint32_t u32fnStateErrorError(void)
00248 {
00249   uint32_t u32Status;
00250   
00251   /* We are not going anywhere. */
00252   u32Status = u32fnSafeMode();
00253   
00254   return (u32Status);
00255 }
00256 /*
00257  ******************************************************************************
00258  * u32fnStateAcquisitionError
00259  ******************************************************************************
00260  */
00261 static uint32_t u32fnStateAcquisitionError(void)
00262 {
00263   uint32_t u32Status;
00264   
00265   if(gu32SMStateStatus & STATUS_CA_FAILED)
00266   {
00267     /* We are not going anywhere. */
00268     u32Status = u32fnSafeMode();
00269   }
00270   else
00271   {
00272     /* Turn on the lamp */
00273     (void)u8fnSBCEnableWarningLamp(TRUE);
00274     
00275     /* One of the satellites or seat-buckles failed and must be disabled */
00276     gu16ActivePSI5Channels
00277         = u16fnErrorRemoveFromList(gu16ActivePSI5Channels,
00278                                    (uint16_t)gu32SMStateStatus);
00279     
00280     if(CLEAR == gu16ActivePSI5Channels)
00281     {
00282       /* Not much more left to do */
00283       u32Status = u32fnSafeMode();
00284     }
00285     else
00286     {
00287       /* Nothing */
00288     }
00289     vfnSMWriteNextState(SM_STATE_DECISION);
00290   }
00291   
00292   return (u32Status);
00293 }
00294 /*
00295  ******************************************************************************
00296  * u32fnStateDecisionError
00297  ******************************************************************************
00298  */
00299 static uint32_t u32fnStateDecisionError(void)
00300 {
00301   uint32_t u32Status;
00302   
00303   u32Status = CLEAR;
00304   
00305   /* Turn on the lamp */
00306   (void)u8fnSBCEnableWarningLamp(TRUE);
00307   
00308   if(gu32SMStateStatus & SBC_TEST_ALL_SAT)
00309   {
00310     /* This case should never be reached, but if it does, we should disable */
00311     /* the failed satellite(s)                                              */
00312     gu16ActivePSI5Channels
00313         = u16fnErrorRemoveFromList(gu16ActivePSI5Channels,
00314                                    (uint16_t)gu32SMStateStatus);
00315     if(CLEAR == gu16ActivePSI5Channels)
00316     {
00317       /* Not much more left to do */
00318       u32Status = u32fnSafeMode();
00319     }
00320     else
00321     {
00322       /* Nothing */
00323     }
00324   }
00325 
00326   vfnSMWriteNextState(SM_STATE_DEPLOYMENT);
00327   
00328   return (u32Status);
00329 }
00330 /*
00331  ******************************************************************************
00332  * u32fnStateDeploymentError
00333  ******************************************************************************
00334  */
00335 static uint32_t u32fnStateDeploymentError(void)
00336 {
00337   uint32_t u32Status;
00338   
00339   u32Status = CLEAR;
00340   
00341   vfnSMWriteNextState(SM_STATE_SYSTEM_TEST);
00342   
00343   /* We will come into this state if there was an inadvertent deployment, */
00344   /* we shall therefore go into a safe-mode.                              */
00345   u32Status = u32fnSafeMode();
00346   
00347   return (u32Status);
00348 }
00349 /*
00350  ******************************************************************************
00351  * u32fnStateSystemTestError
00352  ******************************************************************************
00353  */
00354 static uint32_t u32fnStateSystemTestError(void)
00355 {
00356   uint32_t u32Status;
00357   
00358   u32Status = CLEAR;
00359   
00360   /* To be developed by customer */
00361   
00362   vfnSMWriteNextState(SM_APPLICATION_START);
00363   
00364   return (u32Status);
00365 }
00366 /*
00367  ******************************************************************************
00368  * u32fnStateGUIError
00369  ******************************************************************************
00370  */
00371 static uint32_t u32fnStateGUIError(void)
00372 {
00373   
00374   uint32_t u32Status;
00375   
00376   u32Status = CLEAR;
00377   
00378   /* GUI state errors can be safely ignored - they're for demo purposes only */
00379   
00380   vfnSMWriteNextState(SM_APPLICATION_START);
00381   
00382   return (u32Status);
00383 }
00384 /*
00385  ******************************************************************************
00386  * u16fnErrorRemoveFromList
00387  ******************************************************************************
00388  */
00389 static uint16_t u16fnErrorRemoveFromList(uint16_t u16Original, uint16_t u16Failed)
00390 {
00391   u16Original &= (uint16_t)~(u16Failed & (BIT11 | BIT10
00392       | BIT9 | BIT8 | BIT7 | BIT6 | BIT5 | BIT4 | BIT3 | BIT2 | BIT1 | BIT0));
00393   return (u16Original);
00394 }
00395 #ifdef USE_LABVIEW
00396 /*
00397  ******************************************************************************
00398  * vfnDisplayGUIErrorMessage
00399  ******************************************************************************
00400  */
00401 static void vfnDisplayGUIErrorMessage(void)
00402 {
00403   vfnLVEnable(TRUE);
00404   (void)u8fnLVWaitForTxPort();
00405   (void)u8fnLabViewSendMSorMP((uint8_t*)&cau8ErrorGUIMsg02, sizeof(cau8ErrorGUIMsg02),
00406                               LV_SEND_SERIALLY, LV_MP_MSG);
00407   vfnLVEnable(CLEAR);
00408   return;
00409 }
00410 #endif
00411 /*
00412  ******************************************************************************
00413  *
00414  *  End of file.
00415  *
00416  ******************************************************************************
00417  */